/**
 * @author Justin Akin
 * @version Action Pals Core Library 0.1.0
 */
package com.actionpals.base
{	
	import com.actionpals.events.CuePointEvent;
	import com.actionpals.events.MetaDataEvent;
	import com.actionpals.events.NetStreamEvent;
	import com.actionpals.events.PlayStatusEvent;
	
	import flash.events.AsyncErrorEvent;
	import flash.events.Event;
	import flash.events.NetStatusEvent;
	import flash.net.NetConnection;
	import flash.net.NetStream;
	import flash.utils.describeType;
	import flash.utils.getQualifiedClassName;
	import flash.utils.getQualifiedSuperclassName;

	public class BaseNetStream extends NetStream implements IBaseInterface
	{
		
	//--------------------------------------------------------------------------------
	//
	//	Public Static Constants
	//
	//--------------------------------------------------------------------------------
		
		public static const BUFFER_EMPTY:String = "NetStream.Buffer.Empty";
		public static const BUFFER_FULL:String = "NetStream.Buffer.Full";
		public static const BUFFER_FLUSH:String = "NetStream.Buffer.Flush";
		public static const PUBLISH_START:String = "NetStream.Publish.Start";
		public static const PUBLISH_BAD_NAME:String = "NetStream.Publish.BadName";
		public static const PUBLISH_IDLE:String = "NetStream.Publish.Idle";
		public static const UNPUBLISH_SUCCESS:String = "NetStream.Unpublish.Success";
		public static const PLAY_START:String = "NetStream.Play.Start";
		public static const PLAY_STOP:String = "NetStream.Play.Stop";
		public static const PLAY_FAILED:String = "NetStream.Play.Failed";
		public static const PLAY_STREAM_NOT_FOUND:String = "NetStream.Play.StreamNotFound";
		public static const PLAY_RESET:String = "NetStream.Play.Reset";
		public static const PLAY_PUBLISH_NOTIFY:String = "NetStream.Play.PublishNotify";
		public static const PLAY_UNPUBLISH_NOTIFY:String = "NetStream.Play.UnpublishNotify";
		public static const PAUSE_NOTIFY:String = "NetStream.Pause.Notify";
		public static const UNPAUSE_NOTIFY:String = "NetStream.Unpause.Notify";
		public static const RECORD_START:String = "NetStream.Record.Start";
		public static const RECORD_NO_ACCESS:String = "NetStream.Record.NoAccess";
		public static const RECORD_STOP:String = "NetStream.Record.Stop";
		public static const RECORD_FAILED:String = "NetStream.Record.Failed";
		public static const SEEK_FAILED:String = "NetStream.Seek.Failed";
		public static const SEEK_INVALID_TIME:String = "NetStream.Seek.InvalidTime";
		public static const SEEK_NOTIFY:String = "NetStream.Seek.Notify";
		
	//--------------------------------------------------------------------------------
	//
	//	Protected Member Variables
	//
	//--------------------------------------------------------------------------------
		
		protected var _eventsBubble:Boolean = true;
		protected var _eventsCancelable:Boolean = true;
		
	//--------------------------------------------------------------------------------
	//
	//	Constructor
	//
	//--------------------------------------------------------------------------------
		
		/**
		 * Constructor
		 */
		public function BaseNetStream( conn:NetConnection ):void
		{	
			super( conn );
			client = this;
			addEventListener( NetStatusEvent.NET_STATUS, onNetStatus );
		}
		
	//--------------------------------------------------------------------------------
	//
	//	Public Methods
	//
	//--------------------------------------------------------------------------------
		
		/**
		 * 
		 */
		public function onCuePoint( data:Object ):void
		{
			var event:CuePointEvent = new CuePointEvent( CuePointEvent.CUE_POINT, _eventsBubble, _eventsCancelable );
			event.data = data;
			dispatchEvent( event );
		}
		
		/**
		 * 
		 */
		public function onMetaData( data:Object ):void
		{
			var event:MetaDataEvent = new MetaDataEvent( MetaDataEvent.DATA_AVAILABLE, _eventsBubble, _eventsCancelable );
			event.data = data;
			dispatchEvent( event );
		}
		
		/**
		 * 
		 */
		public function onPlayStatus( data:Object ):void
		{
			var event:PlayStatusEvent = new PlayStatusEvent( PlayStatusEvent.STATUS, _eventsBubble, _eventsCancelable );
			event.data = data;
			dispatchEvent( event );			
		}
		
	//--------------------------------------------------------------------------------
	//
	//	Getters and Setters
	//
	//--------------------------------------------------------------------------------
		
		public function set eventsBubble( val:Boolean ):void
		{
			_eventsBubble = val;
		}
		
		public function set eventsCancelable( val:Boolean ):void
		{
			_eventsCancelable = val;
		}
		
		/**
		 * Returns a fully qualifed class name of BaseClass or any subclass.
		 * @return String		Returns a fully qualifed class name of BaseClass or
		 * 						any subclass.
		 */
		public function get qualifiedClassName():String
		{
			return getQualifiedClassName( this );
		}
		
		/**
		 * Returns a fully qualifed class name of BaseClass or any subclass.
		 * @return A fully qualified class name.
		 */
		public function get qualifiedSuperclassName():String
		{
			return getQualifiedSuperclassName( this );
		}
		
		/**
		 * Returns a fully qualifed class name of BaseClass or any subclass.
		 * @return String A fully qualified class name.
		 */
		public function get typeDescription():XML
		{
			return describeType( this );
		}
		
	//--------------------------------------------------------------------------------
	//
	//	Event Handlers
	//
	//--------------------------------------------------------------------------------
		
		/**
		 * 
		 */
		protected function onAsyncError( event:AsyncErrorEvent ):void
		{
			var newEvent:Event = event.clone();
			dispatchEvent( newEvent );
		}
		
		/**
		 * 
		 */
		protected function onNetStatus( event:NetStatusEvent ):void
		{	
			var code:String;
			var nsEvent:NetStreamEvent;
			
			switch ( event.info.code )
			{	
                case BUFFER_EMPTY:
                
                    code = NetStreamEvent.BUFFER_EMPTY;
                    break;
                    
                 case BUFFER_FULL:
                
                    code = NetStreamEvent.BUFFER_FULL;
                    break;
                    
                 case BUFFER_FLUSH:
                
                    code = NetStreamEvent.BUFFER_FLUSH;
                    break;
                    
                 case PUBLISH_START:
                
                    code = NetStreamEvent.PUBLISH_START;
                    break;
                    
                 case PUBLISH_BAD_NAME:
                
                    code = NetStreamEvent.PUBLISH_BAD_NAME;
                    break;
                    
                 case PUBLISH_IDLE:
                
                    code = NetStreamEvent.PUBLISH_IDLE;
                    break;
                    
                 case UNPUBLISH_SUCCESS:
                
                    code = NetStreamEvent.UNPUBLISH_SUCCESS;
                    break;
                    
                 case PLAY_START:
                
                    code = NetStreamEvent.PLAY_START;
                    break;
                    
                 case PLAY_STOP:
                
                    code = NetStreamEvent.PLAY_STOP;
                    break;
                    
                 case PLAY_FAILED:
                
                    code = NetStreamEvent.PLAY_FAILED;
                    break;
                    
                 case PLAY_STREAM_NOT_FOUND:
                
                    code = NetStreamEvent.PLAY_STREAM_NOT_FOUND;
                    break;
                    
                 case PLAY_RESET:
                
                    code = NetStreamEvent.PLAY_RESET;
                    break;
                    
                 case PLAY_PUBLISH_NOTIFY:
                
                    code = NetStreamEvent.PLAY_PUBLISH_NOTIFY;
                    break;
                    
                 case PLAY_UNPUBLISH_NOTIFY:
                
                    code = NetStreamEvent.PLAY_UNPUBLISH_NOTIFY;
                    break;
                    
                 case PAUSE_NOTIFY:
                
                    code = NetStreamEvent.PAUSE_NOTIFY;
                    break;
                    
                 case UNPAUSE_NOTIFY:
                
                    code = NetStreamEvent.UNPAUSE_NOTIFY;
                    break;
                    
                 case RECORD_START:
                
                    code = NetStreamEvent.RECORD_START;
                    break;
                    
                 case RECORD_NO_ACCESS:
                
                    code = NetStreamEvent.RECORD_NO_ACCESS;
                    break;
                    
                 case RECORD_STOP:
                
                    code = NetStreamEvent.RECORD_STOP;
                    break;
                    
                 case RECORD_FAILED:
                
                    code = NetStreamEvent.RECORD_FAILED;
                    break;
                    
                 case SEEK_FAILED:
                
                    code = NetStreamEvent.SEEK_FAILED;
                    break;
                    
                 case SEEK_INVALID_TIME:
                
                    code = NetStreamEvent.SEEK_INVALID_TIME;
                    break;
                    
                 case SEEK_NOTIFY:
                
                    code = NetStreamEvent.SEEK_NOTIFY;
                    break;
                    
            }
            
            nsEvent = new NetStreamEvent( code, _eventsBubble, _eventsCancelable );
            dispatchEvent( nsEvent );
		}			
	}
}